<?php

namespace App\Http\Controllers\WorkOrder;

use App\Enums\WorkOrder\ErrCode;
use App\Enums\WorkOrder\OrderEnum;
use App\Exceptions\Custom\CustomHttpResponseException;
use App\Http\Controllers\BaseController;
use App\Http\Middleware\OpenShop\MerchantAppAuth;
use App\Http\Validate\AbstractBaseValidate;
use App\Models\Common\ConfigModel;
use App\Models\Common\ResourcesModel;
use App\Models\Workflow\WorkflowV2OrderModel;
use App\Models\WorkOrder\WorkOrderApplyContentModel;
use App\Models\WorkOrder\WorkOrderApplyMainModel;
use App\Models\WorkOrder\WorkOrderUserRoleModel;
use App\Rules\Mobile;
use App\Service\Cruise\Mission\WorkflowV2InputService;
use App\Service\OpenShop\Merchant\MerchantAuth;
use App\Service\WorkOrder\ProblemFeedbackService;
use App\Service\WorkOrder\Reject\WorkOrderRejectService;
use App\Service\WorkOrder\Web\ProblemFeedbackWebService;
use App\Service\WorkOrder\WorkOrderBaseService;
use App\Support\CustomForm\AttributeWorkOrderSupport;
use App\Support\CustomForm\ValidateSupport;
use Illuminate\Http\JsonResponse;
use Illuminate\Http\Request;
use Illuminate\Validation\ValidationException;
use Psr\Container\ContainerExceptionInterface;
use Psr\Container\NotFoundExceptionInterface;

class ProblemFeedbackController extends BaseController
{
    /*
     * 问题反馈父级列表
     */
    public function problemList()
    {
        return $this->success(ProblemFeedbackService::problemList());
    }

    /*
     * 问题反馈分类
     */
    public function problemType(): JsonResponse
    {
        return $this->success(ProblemFeedbackService::problemType());
    }

    public function getProblemForm(Request $request)
    {
        $this->validate($request, [
            'problemType'  => 'required|numeric',
            'problemValue' => 'numeric',
        ]);
        //获取表单
        $problemType  = $request->get('problemType');
        $problemValue = $request->get('problemValue');
        $shopId       = $request->header('shopId', 0);

        //特殊判断处理返回值 目前是写死的
        if ($problemType == OrderEnum::PROBLEM_PID_4 && in_array($problemValue, [
                OrderEnum::PROBLEM_PID_4_CHILDREN_3,
                OrderEnum::PROBLEM_PID_4_CHILDREN_4,
                OrderEnum::PROBLEM_PID_4_CHILDREN_9
            ])) {
            $contactConfig = ConfigModel::query()
                                        ->where('module', 'workOrder')
                                        ->where('name', 'monitoringContact')
                                        ->value('value');
            $data          = [];
            if ($contactConfig) {
                $data = json_decode($contactConfig, true)[$problemType][$problemValue] ?? [];
            }
            return $this->fail(BaseController::RESPONSE_HTTP_WORK_ORDER_SPECIAL_CODE, '', $data);
        }

        $userMobile = getRmsUserInfoByAuth()->mobile ?? '';

        $form = ProblemFeedbackService::getProblemForm(
            $request->problemType, $problemValue, $shopId, [],
            OrderEnum::PROBLEM_FEEDBACK_INFO_USE_APP, '', $userMobile,
        );
        return $this->success($form);
    }

    /**
     * @param Request $request
     * @return JsonResponse
     * @throws ValidationException
     * @throws ContainerExceptionInterface
     * @throws NotFoundExceptionInterface
     */
    public function getBackendProblemForm(Request $request): JsonResponse
    {
        $this->validate($request, [
            'problemType'  => 'required|numeric',
            'problemValue' => 'numeric',
            'shopId'       => "required|int|gt:0"
        ]);
        //获取表单
        $problemType  = $request->get('problemType');
        $problemValue = $request->get('problemValue');
        $shopId       = $request->get('shopId');

        //特殊判断处理返回值 目前是写死的
        if ($problemType == OrderEnum::PROBLEM_PID_4 && in_array($problemValue, [
                OrderEnum::PROBLEM_PID_4_CHILDREN_3,
                OrderEnum::PROBLEM_PID_4_CHILDREN_4,
                OrderEnum::PROBLEM_PID_4_CHILDREN_9
            ])) {
            $contactConfig = ConfigModel::query()
                                        ->where('module', 'workOrder')
                                        ->where('name', 'monitoringContact')
                                        ->value('value');
            $data          = [];
            if ($contactConfig) {
                $data = json_decode($contactConfig, true)[$problemType][$problemValue] ?? [];
            }
            return $this->fail(BaseController::RESPONSE_HTTP_WORK_ORDER_SPECIAL_CODE, '', $data);
        }

        $userMobile = getRmsUserInfoByAuth()->mobile ?? '';

        $userId = getRmsUserId();
        $form   = ProblemFeedbackService::getProblemForm(
            $request->problemType, $problemValue, $shopId, [],
            OrderEnum::PROBLEM_FEEDBACK_INFO_USE_APP, '', $userMobile, $userId, 1,
        );


        if (!in_array($problemType, OrderEnum::PROBLEM_NOT_NEED_HANDLE)) {
            $role        = OrderEnum::PROBLEM_PID_TO_ROLE[$problemType];
            $managerList = WorkOrderUserRoleModel::query()->getUsersByRole(
                $role, $problemType, $problemValue,
            );
            $nextForm    = WorkOrderBaseService::singleFormBuild(
                'handle',
                AttributeWorkOrderSupport::INPUT_TYPE_SELECT_MULTIPLE,
                WorkOrderUserRoleModel::ROLE_TYPE_TEXT[$role] ?? '处理人',
            )->setCustomAttribute(
                ['icon', 'arrow-right'],
            )->setValidateRules(
                ValidateSupport::getInstance(true),
            )->setCustomAttribute(
                ['options', $managerList],
            )->setValue(null)->build();

            $form['form'] = array_merge($form['form'], [$nextForm]);
        }

        $form["form"] = collect($form["form"])->map(function ($attribute) {
            if (in_array(
                $attribute["inputType"],
                [
                    AttributeWorkOrderSupport::INPUT_TYPE_ALBUM_CHECKBOX,
                    AttributeWorkOrderSupport::INPUT_TYPE_ALBUM_RADIO,
                    AttributeWorkOrderSupport::INPUT_TYPE_VIDEO_RADIO,
                    AttributeWorkOrderSupport::INPUT_TYPE_VIDEO_CHECK_BOX,
                ])
            ) {
                $required = $attribute["validate"]["required"] ?? false;
                if ($required == true) {
                    $attribute["validate"]["required"] = false;
                }
            }
            return $attribute;
        })->values()->toArray();

        return $this->success($form);
    }

    public function getProblemDetail(Request $request, string $workOrderNo)
    {
        [$problemInfo, $_, $arguments, $_, $_] = ProblemFeedbackWebService::baseWorkOrderInfo($workOrderNo);

        $form = ProblemFeedbackService::getProblemForm($problemInfo->problemPid, $problemInfo->problemChildId,
            $problemInfo->shopId, $arguments, OrderEnum::PROBLEM_FEEDBACK_INFO_USE_WEB, $workOrderNo);

        foreach ($form['form'] as $k => $item) {
            if (in_array($item['field'], OrderEnum::FORM_SPECIAL_ITEM)) {
                unset($form['form'][$k]);
            }
        }

        $form['form']      = array_values($form['form']);
        $form['status']    = $problemInfo->status;
        $form['childStep'] = $problemInfo->childStep;

        return $this->success($form);
    }

    public function getOrmOrderGoods(Request $request)
    {
        $this->validate($request, [
            'ormOrderId' => 'required|string'
        ]);
        //获取商品列表
        return $this->success(ProblemFeedbackService::getOrmOrderGoods($request->ormOrderId));
    }

    public function addWorkOrder(Request $request)
    {
        //数据校验
        $this->validate($request, [
            'problemPid'     => 'required|numeric',
            'problemChildId' => 'required|numeric',
            'driverPhone'    => new Mobile(),
            'workOrderNo'    => 'string',
        ]);

        $shopId = $request->header('shopId');
        ProblemFeedbackService::addWorkOrder($request->all(), $shopId, MerchantAppAuth::$userId);
        return $this->success();
    }

    /**
     * 获得工单V2详情
     * @param Request $request
     * @param $value
     * @return JsonResponse
     */
    public function getWorkOrderV2(Request $request, $value): JsonResponse
    {
        $shopId     = $request->header('shopId');
        $formData   = ProblemFeedbackService::getWorkOrderV2($value, $shopId, MerchantAppAuth::$userId);
        return $this->success($formData);
    }

    /**
     * 分步提交表单信息
     * @param Request $request
     * @param $id
     * @return JsonResponse
     * @throws ValidationException
     */
    public function stepSubmitWorkOrderV2(Request $request, $id): JsonResponse
    {
        $this->validate($request, [
            'field' => 'required|string',
            'value' => 'required',
        ]);

        $field = $request->post('field');
        $value = $request->post('value');

        // 获得cruiseOrderId
        $cruiseOrderId = (int)WorkflowV2OrderModel::query()->where('id', $id)->value('submitCruiseOrderId');

        if (!$cruiseOrderId) {
            return $this->fail(400, '该工单不存在');
        }

        (new WorkflowV2InputService($cruiseOrderId, MerchantAppAuth::$userId))->saveUserContentJson($field, $value);

        return $this->success();
    }

    /**
     * 提交表单信息
     * @param Request $request
     * @param $id
     * @return JsonResponse
     */
    public function submitWorkOrderV2(Request $request, $id): JsonResponse
    {
        // 获得cruiseOrderId
        $cruiseOrderId = (int)WorkflowV2OrderModel::query()->where('id', $id)->value('submitCruiseOrderId');

        if (!$cruiseOrderId) {
            return $this->fail(400, '该工单不存在');
        }

        (new WorkflowV2InputService($cruiseOrderId, MerchantAppAuth::$userId))->setWorkflowOrderId($id)->submitOrder();

        return $this->success();
    }

    /**
     * @param Request $request
     * @return JsonResponse
     * @throws ValidationException
     */
    public function backendAddProblemWorkOrder(Request $request)
    {
        //数据校验
        $this->validate($request, [
            'problemPid'     => 'required|numeric',
            'problemChildId' => 'required|numeric',
            'driverPhone'    => new Mobile(),
            'workOrderNo'    => 'string',
            "shopId"         => "required|int|gt:0",
            "sourceType"     => AbstractBaseValidate::intInValidateBuild(
                true,
                WorkOrderApplyMainModel::SOURCE_TYPE_TEXT,
            ),
            "completeTime"   => [
                AbstractBaseValidate::timeValidateBuild(true)
            ],
            "isCompleted"    => AbstractBaseValidate::intInValidateBuild(
                true,
                ["0" => "待解决", "1" => "已解决"],
            ),
            "solution"       => "string"
        ]);

        return $this->success(ProblemFeedbackService::addWorkOrder(
            $request->all(),
            $request->shopId,
            $request->user()->id,
            true,
        ));
    }

    public function feedbackProgressLists(Request $request)
    {
        $shopId   = $request->header('shopId');
        $pageNum  = $request->get('pageNum', 1);
        $pageSize = $request->get('pageSize', 15);

        return $this->success(ProblemFeedbackService::feedbackProgressLists($shopId, $pageNum, $pageSize));
    }

    public function feedbackProgressDetail(Request $request, string $workOrderNo)
    {
        return $this->success(['detail' => ProblemFeedbackService::feedbackProgressDetail($workOrderNo)]);
    }

    /**
     * 获得工单V2详情
     * @param Request $request
     * @param string $workOrderNo
     * @return JsonResponse
     */
    public function feedbackProgressDetailV2(Request $request, string $workOrderNo): JsonResponse
    {
        return $this->success(ProblemFeedbackService::feedbackProgressDetailV2($workOrderNo));
    }

    public function topTips(Request $request)
    {
        $shopId = $request->header('shopId');
        $request->replace(['shopId' => $shopId]);

        $this->validate($request, [
            'shopId' => "required|integer|min:1",
        ]);

        $userId = MerchantAppAuth::$userId;

        return $this->success(WorkOrderRejectService::rejectDetails($shopId, $userId));
    }
}
